import java.util.List;

import SFT.*;

/* the Class responsible to handling the Tuner option of the Project*/
public class Tuner {
	
	final static double period = 0.5;
	
	
	/*
	 * the Tuner function. given a Wav file prints the list of notes closest to the given input and the
	 * error of each one, both for the consecutive time periods of 0.5 seconds.
	 */
	public static void tuneWAVFile(String wavFile){
		WavFileInfo outSFT = Integration.GetFrequencies(wavFile, period);//running the SFT algorithm on the given wavFile, with half a second period
		List<Double> frequencies = Integration.GetFreqListFromWavFileInfo(outSFT);
		double seconds = 0;
		for(double freq : frequencies){
			System.out.println("in " + seconds + ": ");
			seconds += period;
			tuneFreq(freq);
		}
	}
	
	/*
	 * calculates the error of the given frequency from it's closest music note
	 */
	private static double percentOfMistake(double freq, FreqNote note){
		FreqNote middle = new FreqNote(note);
		if (freq < note.getFreqOfNote())
			middle.decreaseByQuaterTune();
		else if(freq > note.getFreqOfNote())
			middle.increaseByQuaterTune();
		else
			return 0;
		double freq2note = freq - note.getFreqOfNote();
		double middle2note = middle.getFreqOfNote() - note.getFreqOfNote();
		double ret = freq2note / middle2note;
		ret = Math.abs(ret);
		return ret;
	}
	
	
	/*
	 * the tuner functions, given a frequency prints the appropriate note, it's octave
	 *  and the error of the frequency from the note
	 */
	private static void tuneFreq(double freq){
		
		FreqNote note = Note.findClosestNote(freq);
		if (note.isSilence()) {
			System.out.println("There was silence.");
		}
		else {
			double error = 100 * percentOfMistake(freq, note);
			System.out.println("You sang: " + freq);
			System.out.println("The closest note is: " + note.getNote() + ", of Octava : " + note.getFreqNoteOct() + ". It's frequencey is: " + note.getFreqOfNote() + ", and the error in percents is: " + error);
			if (error != 0) {
				if (freq < note.getFreqOfNote()) {
					System.out.println("Your note was too low.");
				}
				if (freq > note.getFreqOfNote()) {
					System.out.println("Your note was too high.");
				}
			}
		}
	}

}
